package com.walter.controller;

import cn.hutool.core.date.DateUnit;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.NumberUtil;
import com.sun.management.OperatingSystemMXBean;
import com.walter.Application;
import com.walter.common.BaseController;
import com.walter.common.Result;
import com.walter.exception.LogicException;
import com.walter.model.vo.JVMInfo;
import com.walter.model.vo.ServerMonitorInfo;
import com.walter.util.Kv;
import com.walter.util.MyCommon;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.io.File;
import java.lang.management.ClassLoadingMXBean;
import java.lang.management.ManagementFactory;
import java.lang.management.ThreadMXBean;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * @author ：ch
 * @date ：Created in 2021/5/25
 * @description：
 * @modified By：
 * @version: 1.0
 */
@RestController
@RequestMapping("api/systemMonitor")
@Slf4j
public class SystemMonitorController extends BaseController {
    @GetMapping("findJVMInfo") // linux系统待测试
    @ApiOperation("后管 查询JVM信息")
    public Result<JVMInfo> findJVMInfo(){
        JVMInfo retVal = new JVMInfo();
        //线程使用情况
        ThreadMXBean threads = ManagementFactory.getThreadMXBean();
        retVal.setThreadsTotal(threads.getTotalStartedThreadCount()) // JVM总线程数
                .setThreadsLive(threads.getThreadCount()) // JVM当前活跃线程数量
                .setThreadsDaemon(threads.getDaemonThreadCount()) // JVM守护线程数量
                .setThreadsPeak(threads.getPeakThreadCount()); // JVM峰值线程数量
        //类加载情况
        ClassLoadingMXBean cl = ManagementFactory.getClassLoadingMXBean();
        retVal.setClsTotalLoaded(cl.getTotalLoadedClassCount()) // JVM总加载Class数量
                .setClsCurrLoaded(cl.getLoadedClassCount()) // JVM已加载Class数量
                .setClsUnloaded(cl.getUnloadedClassCount()); // JVM未加载Class数量
        return Result.success(retVal.setLastUpdateTime(new Date()));
    }

    @GetMapping("findServerMonitorInfo") // linux系统待测试
    @ApiOperation("后管 查询服务器信息和存储信息")
    public Result<ServerMonitorInfo> findServerMonitorInfo(){
        ServerMonitorInfo retVal = new ServerMonitorInfo();
        Date now = new Date();
        retVal.setLastStartTime(Application.appStartTime)
                .setLastUptime(DateUtil.between(Application.appStartTime,now, DateUnit.SECOND))
                .setLastUpdateTime(now);
        retVal.setCpuCount(Runtime.getRuntime().availableProcessors());// CPU数量
        try {
            retVal.setCpuUsage(MyCommon.getProcessCpuLoad()); // 系统CPU使用率
        }
        catch (Exception e){
            e.printStackTrace();
            log.info("call findServerMonitorInfo() error\n {}",e);
            throw new LogicException(e.toString());
        }
        OperatingSystemMXBean mem = (OperatingSystemMXBean) ManagementFactory.getOperatingSystemMXBean();
        retVal.setTotalRAM(mem.getTotalPhysicalMemorySize() / 1024 / 1024.0)
                .setAvailableRAM(mem.getFreePhysicalMemorySize() / 1024 / 1024.0)
                .setUsedRAM((mem.getTotalPhysicalMemorySize() - mem.getFreePhysicalMemorySize()) / 1024 / 1024.0);
        retVal.setUsedRAMPercent(NumberUtil.round(NumberUtil.div(retVal.getUsedRAM(),retVal.getTotalRAM()) * 100.0,2));
        File[] disks = File.listRoots();
        List<Kv> harddiskInfoList = new ArrayList<>();
        for(File file : disks)
        {
            harddiskInfoList.add(
                    Kv.create().set("driveLetter",file.getPath())
                            .set("total",file.getTotalSpace() / 1024 / 1024)
                            .set("available",file.getUsableSpace() / 1024 / 1024)
                            .set("used",(file.getTotalSpace() - file.getUsableSpace()) / 1024 / 1024)
            );
        }
        return success(retVal.setHarddiskInfoList(harddiskInfoList));
    }
}
